fix GUI handling of track filter start/stop times.
authortsteven4 <13596209+tsteven4@users.noreply.github.com>
Tue, 23 Aug 2022 18:36:22 +0000 (12:36 -0600)
committertsteven4 <13596209+tsteven4@users.noreply.github.com>
Tue, 23 Aug 2022 18:36:22 +0000 (12:36 -0600)
This resolves #915

The timeSpec of the QDateTimeEdit objects is maintained in
accordance with the TZCheck QCheckBox.  This solves additional
issues with DST transitions and edits.

gui/filterdata.cc
gui/filterdata.h
gui/filterwidgets.cc
gui/filterwidgets.h

index f0ff55f9b01d6e111aaad9c36b7ab67fe5df7833..0003c83ce9039f08b5b0b04a289fbc6ecee99421 100644 (file)
@@ -55,14 +55,9 @@ QStringList WayPtsFilterData::makeOptionString()
 }
 
 //------------------------------------------------------------------------
-static QString optionDate(const QDateTime& dt, bool useLocal)
+static QString optionDate(const QDateTime& dt)
 {
-  QDateTime d;
-  if (useLocal) {
-    d = dt.toLocalTime();
-  } else {
-    d = dt.toUTC();
-  }
+  QDateTime d = dt.toUTC();
 
   QDate date = d.date();
   QTime time = d.time();
@@ -130,10 +125,10 @@ QStringList TrackFilterData::makeOptionString()
   }
 
   if (start) {
-    s += QString(",start=%1").arg(optionDate(startTime, TZ));
+    s += QString(",start=%1").arg(optionDate(startTime));
   }
   if (stop) {
-    s += QString(",stop=%1").arg(optionDate(stopTime, TZ));
+    s += QString(",stop=%1").arg(optionDate(stopTime));
   }
   if (move) {
     s += QString(",move=%1w%2d%3h%4m%5s").arg(weeks).arg(days).arg(hours).arg(mins).arg(secs);
index 73018734767321d908f4270e2279e952edde3193..00071541dd439572e442fc87d3443bd7486b9825 100644 (file)
@@ -61,7 +61,7 @@ class TrackFilterData: public FilterData
 public:
   TrackFilterData():  title(false), titleString(QString()),
     move(false),  weeks(0), days(0), hours(0), mins(0), secs(0),
-    TZ(false),
+    TZ(true),
     start(false),
     stop(false),
     pack(false), merge(false), split(false),
index a71ab88b494b94ea18edc8574060786e7d209ff2..d6d5aa17b8044d704181d400a3bb576d3510cb93 100644 (file)
 //
 
 #include "filterwidgets.h"
-#include <limits>
+
+#include <assert.h>      // for assert
+#include <limits>        // for numeric_limits
+
+#include <QChar>         // for QChar
+#include <QCheckBox>     // for QCheckBox
+#include <QEvent>        // for QEvent, QEvent::LocaleChange
+#include <QLabel>        // for QLabel
+#include <QRadioButton>  // for QRadioButton
+#include <Qt>            // for LocalTime, UTC
 
 
 //------------------------------------------------------------------------
@@ -60,9 +69,24 @@ TrackWidget::TrackWidget(QWidget* parent, TrackFilterData& tfd): FilterWidget(pa
   connect(ui.splitTimeCheck,   &QAbstractButton::clicked, this, &TrackWidget::splitTimeX);
   connect(ui.splitDistanceCheck,   &QAbstractButton::clicked, this, &TrackWidget::splitDistanceX);
 
+  connect(ui.TZCheck, &QAbstractButton::clicked, this, &TrackWidget::TZX);
+
   ui.startEdit->setDisplayFormat("dd MMM yyyy hh:mm:ss AP");
   ui.stopEdit->setDisplayFormat("dd MMM yyyy hh:mm:ss AP");
 
+  assert(tfd.startTime.timeSpec() == tfd.stopTime.timeSpec());
+  assert((tfd.startTime.timeSpec() == Qt::UTC) || (tfd.startTime.timeSpec() == Qt::LocalTime));
+  // Qt5 QDateTimeEdit::setDateTime ignored the passed QDateTime::timeSpec.
+  // Qt6 QDateTimeEdit::setDateTime will convert the passed QDateTime if the passed
+  // QDateTime::timeSpec doesn't match QDateTimeEdit::timeSpec.
+  // If the two timeSpecs match Qt5 and Qt6 behave the same.
+  ui.startEdit->setTimeSpec(tfd.startTime.timeSpec());
+  ui.stopEdit->setTimeSpec(tfd.stopTime.timeSpec());
+  // Force TZ data to be in sync with startTime & stopTime time spec.
+  // This makes sure the initial state of the TZCheck box is in agreement
+  // with the startTime::timeSpec and stopTime::timeSpec.
+  tfd.TZ = tfd.startTime.timeSpec() == Qt::LocalTime;
+
   // Collect the data fields.
   fopts << new BoolFilterOption(tfd.title,  ui.titleCheck);
   fopts << new BoolFilterOption(tfd.move,   ui.moveCheck);
@@ -157,6 +181,22 @@ void TrackWidget::splitDistanceX()
   }
   otherCheckX();
 }
+//------------------------------------------------------------------------
+void TrackWidget::TZX()
+{
+  if (ui.TZCheck->isChecked()) {
+    ui.startEdit->setTimeSpec(Qt::LocalTime);
+    ui.stopEdit->setTimeSpec(Qt::LocalTime);
+  } else {
+    ui.startEdit->setTimeSpec(Qt::UTC);
+    ui.stopEdit->setTimeSpec(Qt::UTC);
+  }
+  // Force update of Edit displays, so the displayed
+  // datetimes are in sync with the specified time spec.
+  auto ev = QEvent(QEvent::LocaleChange);
+  ui.startEdit->event(&ev);
+  ui.stopEdit->event(&ev);
+}
 
 
 //------------------------------------------------------------------------
index 088ca0ae85250ec3281522481a3d81543e21ef95..7de8ea1ecf57615195da0da0c9ca9db5a0d4d84c 100644 (file)
 #ifndef FILTERWIDGETS_H
 #define FILTERWIDGETS_H
 
+#include <QAbstractButton>   // for QAbstractButton
+#include <QComboBox>         // for QComboBox
+#include <QDateTime>         // for QDateTime
+#include <QDateTimeEdit>     // for QDateTimeEdit
+#include <QDoubleValidator>  // for QDoubleValidator
+#include <QFunctionPointer>  // for qMax, qMin
+#include <QLineEdit>         // for QLineEdit
+#include <QList>             // for QList
+#include <QObject>           // for QObject, Q_OBJECT, slots
+#include <QSpinBox>          // for QSpinBox
+#include <QString>           // for QString
+#include <QWidget>           // for QWidget
+
+#include "filterdata.h"      // for MiscFltFilterData, RtTrkFilterData, TrackFilterData, WayPtsFilterData
+#include "ui_miscfltui.h"    // for Ui_MiscFltWidget
+#include "ui_rttrkui.h"      // for Ui_RtTrkWidget
+#include "ui_trackui.h"      // for Ui_TrackWidget
+#include "ui_wayptsui.h"     // for Ui_WayPtsWidget
 
-#include "ui_trackui.h"
-#include "ui_wayptsui.h"
-#include "ui_rttrkui.h"
-#include "ui_miscfltui.h"
-#include "filterdata.h"
 
-class CheckEnabler;
-class FilterOption;
 //------------------------------------------------------------------------
 class CheckEnabler: public QObject
 {
@@ -307,6 +318,7 @@ private slots:
   void splitDateX();
   void splitTimeX();
   void splitDistanceX();
+  void TZX();
   void packCheckX();
 };